package at.tuwien.seminar.scrum1.proxies;

import at.tuwien.seminar.scrum1.hibernate.HibernateUtil;
import at.tuwien.seminar.scrum1.model.Customer;
import at.tuwien.seminar.scrum1.model.Reservation;
import at.tuwien.seminar.scrum1.model.Room;


import javax.persistence.EntityManager;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

public class ReservationProxy {

	private static ReservationProxy instance;
	private EntityManager em;

	private ReservationProxy() {
		em = HibernateUtil.getEntityManagerFactory().createEntityManager();
	}

	public static ReservationProxy getInstance() {
		return instance == null ? instance = new ReservationProxy() : instance;
	}

	public List<Reservation> getAll() {
       	
		return getAll(em);
	}
	
	public List<Reservation> getAll(EntityManager em) {
       	return (List<Reservation>)em.createQuery("from Reservation").getResultList();
     
	}


    public List<Reservation> getReservationByCustomer(Customer customer) {
            return (List<Reservation>)em.createQuery("select r from Reservation r, IN (r.customers) c WHERE c.id=:id").setParameter("id", customer.getId()).getResultList();
    }

    public List<Reservation> getReservationByRoom(Room room) {
            return (List<Reservation>)em.createQuery("from Reservation where room.id=:id").setParameter("id", room.getId()).getResultList();
    }
    
    public boolean checkReservationDate(Room room, Date start, Date end){
    	List result= em.createQuery("" +
    			"from Reservation " +
    			"where room.id=:id " +
    			"AND ((:start BETWEEN startDate AND endDate) " +
    			"OR (:end BETWEEN startDate AND endDate))")
    			.setParameter("id", room.getId())
    			.setParameter("start", start)
    			.setParameter("end",end).getResultList();
    	
    	return result.isEmpty();
    }

	public long insertReservation(Reservation reservation)
	{
		return insertReservation(reservation, em);
	}
	
	public long insertReservation(Reservation reservation, EntityManager em)
	{
		em.getTransaction().begin();
        reservation.setClosed(false);
		em.persist(reservation);
		em.getTransaction().commit();
		
		return reservation.getId();
	}
	
	public Reservation updateReservation(Reservation reservation)
	{
		return updateReservation(reservation, em);
	}
	
	public Reservation updateReservation(Reservation reservation, EntityManager em)
	{
		em.getTransaction().begin();
		em.merge(reservation);
		em.getTransaction().commit();
		
		return reservation;
	}


    public void deleteReservation(Reservation reservation) {
        deleteReservation(reservation, em);
    }

    public void deleteReservation(Reservation reservation, EntityManager em) {
        em.getTransaction().begin();
		em.remove(reservation);
		em.getTransaction().commit();
    }



}
